﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;

using System.Text;
using System.Windows.Forms;
using RemoteGacutil.Logic;
using System.IO;
using System.Diagnostics;

namespace RemoteGacutil
{
    public partial class MainForm : Form
    {

        private enum AssemblyOrderBy
        {
            Name,
            Version,
            Culture,
            PublicKeyToken,
        }


        private class CachedAssemblyComparer : IComparer<CachedAssembly>
        {

            private AssemblyOrderBy _orderBy;

            public CachedAssemblyComparer(AssemblyOrderBy orderBy)
            {
                _orderBy = orderBy;
            }

            #region IComparer<CachedAssembly> Membri di

            public int Compare(CachedAssembly x, CachedAssembly y)
            {
                switch (_orderBy)
                {
                    case AssemblyOrderBy.Name:
                        return String.Compare(
                            x.AssemblyName + x.Version,
                            y.AssemblyName + y.Version
                            );
                    case AssemblyOrderBy.Version:
                        return String.Compare(
                            x.Version + x.AssemblyName + x.Version,
                            y.Version + y.AssemblyName + y.Version
                            );
                    case AssemblyOrderBy.Culture:
                        return String.Compare(
                            x.Culture,
                            y.Culture
                            );
                    case AssemblyOrderBy.PublicKeyToken:
                        return String.Compare(
                            x.PublicKeyToken + x.AssemblyName + x.Version,
                            y.PublicKeyToken + y.AssemblyName + y.Version
                            );
                    default:
                        return 0;
                }
            }

            #endregion
        }


        private List<CachedAssembly> _asmCache;

        public MainForm()
        {
            InitializeComponent();
            listAssembliesBtn_Click(this, new EventArgs());
        }

        private void listAssembliesBtn_Click(object sender, EventArgs e)
        {
            if (!string.IsNullOrEmpty(serverTb.Text))
            {
                GacUtil g = new GacUtil(serverTb.Text);
                _asmCache = g.GetCachedAssemblies();
                statusLabel.Text = "Listing " + _asmCache.Count.ToString() + " assemblies";
                OrderAssembliesBy(AssemblyOrderBy.Name);
                LoadAssemblies();
            }
            else
            {
                serverTb.Focus();
            }
        }

        private void LoadAssemblies()
        {
            asmList.Items.Clear();
            foreach (CachedAssembly asm in _asmCache)
            {
                ListViewItem item = new ListViewItem();
                item.Text = asm.AssemblyName;
                item.SubItems.Add(asm.Version);
                item.SubItems.Add(asm.Culture);
                item.SubItems.Add(asm.PublicKeyToken);
                asmList.Items.Add(item);
            }
        }

        private void OrderAssembliesBy(AssemblyOrderBy column)
        {
            CachedAssemblyComparer comparer = new CachedAssemblyComparer(column);
            _asmCache.Sort(comparer);
        }

        private void installBtn_Click(object sender, EventArgs e)
        {
            if (!string.IsNullOrEmpty(serverTb.Text))
            {
                openFileDialog.InitialDirectory = Directory.GetCurrentDirectory();
                if (openFileDialog.ShowDialog() == DialogResult.OK)
                {
                    new GacUtil(serverTb.Text).Install(openFileDialog.FileName);
                    MessageBox.Show("Assembly successfully installed");
                }
            }
            else
            {
                serverTb.Focus();
            }
        }

        private void uninstallBtn_Click(object sender, EventArgs e)
        {
            if (asmList.SelectedItems.Count > 0)
            {
                if (MessageBox.Show("Uninstall " + _asmCache[asmList.SelectedIndices[0]].CacheEntry + " ?", "Approve", MessageBoxButtons.YesNo, MessageBoxIcon.Warning, MessageBoxDefaultButton.Button2) == DialogResult.Yes)
                {
                    new GacUtil(serverTb.Text).Uninstall(_asmCache[asmList.SelectedIndices[0]].CacheEntry);
                    MessageBox.Show("Assembly successfully UNinstalled");
                }
            }
        }

        private void linkLabel1_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            Process.Start("http://www.evcil.net");
        }

        private void aboutBtn_Click(object sender, EventArgs e)
        {
            new AboutForm().ShowDialog();
        }

        private void asmList_ColumnClick(object sender, ColumnClickEventArgs e)
        {
            AssemblyOrderBy orderBy;
            switch (e.Column)
            {
                case 0: orderBy = AssemblyOrderBy.Name; break;
                case 1: orderBy = AssemblyOrderBy.Version; break;
                case 2: orderBy = AssemblyOrderBy.Culture; break;
                case 3: orderBy = AssemblyOrderBy.PublicKeyToken; break;
                default: return;
            }
            OrderAssembliesBy(orderBy);
            LoadAssemblies();
        }

    }
}
